package com.decent.manager.system.service.impl;

import cn.hutool.core.util.BooleanUtil;
import cn.hutool.core.util.StrUtil;
import cn.hutool.extra.pinyin.PinyinUtil;
import com.decent.common.bo.SimpleMessage;
import com.decent.common.entity.manager.SystemMenu;
import com.decent.common.entity.manager.SystemRole;
import com.decent.common.enums.CommonStatusEnum;
import com.decent.common.enums.ErrorCodeEnum;
import com.decent.manager.config.security.context.LoginContext;
import com.decent.manager.system.auth.service.CleanAuthService;
import com.decent.manager.system.dao.SystemRoleDao;
import com.decent.manager.system.dao.SystemRoleMenuDao;
import com.decent.manager.system.dao.SystemUserRoleDao;
import com.decent.manager.system.dto.SystemRoleDTO;
import com.decent.manager.system.service.SystemRoleService;
import com.decent.manager.system.vo.SystemRoleVO;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.collections4.CollectionUtils;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import javax.annotation.Resource;
import java.util.Collections;
import java.util.List;
import java.util.Optional;

/**
 * 系统角色service实现
 *
 * @author wangyan
 **/
@Slf4j
@Service
public class SystemRoleServiceImpl implements SystemRoleService {
    @Resource
    private SystemRoleMenuDao systemRoleMenuDao;
    @Resource
    private SystemUserRoleDao systemUserRoleDao;
    @Resource
    private SystemRoleDao systemRoleDao;
    @Resource
    private CleanAuthService cleanAuthService;
    @Resource
    private LoginContext loginContext;

    /**
     * 查询角色菜单
     *
     * @param roleId 角色id
     * @return list
     */
    @Override
    public List<SystemMenu> getRoleMenus(Long roleId) {
        List<SystemMenu> sysMenus = systemRoleMenuDao.queryRolesMenu(roleId);
        return Optional.ofNullable(sysMenus).orElse(Collections.emptyList());
    }

    /**
     * 查询用户角色
     *
     * @param userId 用户id
     * @return 角色
     */
    @Override
    public SystemRole getUserRole(Long userId) {
        return systemUserRoleDao.queryRoles(userId);
    }

    /**
     * 获取资源列表（INTERFACE级资源不需要返回）
     *
     * @param roleId 角色id
     * @return list
     */
    @Override
    public List<SystemMenu> getMenuList(Long roleId) {
        Long loginUserRoleId = loginContext.getLoginUserRoleId();
        List<SystemMenu> sysMenus = systemRoleMenuDao.queryRolesMenu(roleId == null ?
                (loginContext.isSuperAdmin() ? null : loginUserRoleId) : roleId);
        return Optional.ofNullable(sysMenus).orElse(Collections.emptyList());
    }

    /**
     * 查询角色列表
     *
     * @return list
     */
    @Override
    public List<SystemRoleVO> getRoleList() {
        return systemRoleDao.getRoleList();
    }

    /**
     * 新增角色
     *
     * @param role 新增信息
     * @return SimpleMessage
     */
    @Override
    public SimpleMessage createRole(SystemRoleDTO role) {
        role.setRoleCode(PinyinUtil.getPinyin(role.getRoleName(), ""));
        role.setRoleStatus(CommonStatusEnum.NORMAL);
        // 校验公司内是否有重复角色或编码
        if (BooleanUtil.isTrue(systemRoleDao.existRepeatRole(role))) {
            return new SimpleMessage(ErrorCodeEnum.INVALID_PARAMS, "角色名称或编号已存在，请重新起名");
        }
        role.setCreator(loginContext.getLoginUserName());
        systemRoleDao.createRole(role);
        return new SimpleMessage(ErrorCodeEnum.OK);
    }

    /**
     * 修改角色
     *
     * @param role 修改信息
     * @return SimpleMessage
     */
    @Override
    public SimpleMessage updateRole(SystemRoleDTO role) {
        if (StrUtil.isNotEmpty(role.getRoleName())) {
            role.setRoleCode(PinyinUtil.getPinyin(role.getRoleName(), ""));
            SystemRoleDTO repeatRole = new SystemRoleDTO();
            repeatRole.setId(role.getId());
            repeatRole.setRoleName(role.getRoleName());
            repeatRole.setRoleCode(PinyinUtil.getPinyin(role.getRoleName(), ""));
            repeatRole.setRoleStatus(CommonStatusEnum.NORMAL);
            // 校验公司内是否有重复角色或编码
            if (BooleanUtil.isTrue(systemRoleDao.existRepeatRole(repeatRole))) {
                return new SimpleMessage(ErrorCodeEnum.INVALID_PARAMS, "角色名称或编号已存在，请重新起名");
            }
        }
        role.setLastModifier(loginContext.getLoginUserName());
        systemRoleDao.updateRole(role);
        if (role.getRoleStatus() != null && CommonStatusEnum.SUSPEND == role.getRoleStatus()) {
            cleanAuthService.clearLoginUserCacheByRole(role.getId());
        }
        return new SimpleMessage(ErrorCodeEnum.OK);
    }

    /**
     * 菜单授权
     *
     * @param role 授权信息
     * @return SimpleMessage
     */
    @Transactional(rollbackFor = Exception.class)
    @Override
    public SimpleMessage grantMenu(SystemRoleDTO role) {
        role.setCreator(loginContext.getLoginUserName());
        systemRoleMenuDao.clearRoleMenu(role);
        if (CollectionUtils.isNotEmpty(role.getGrantMenuIdList())) {
            role.getGrantMenuIdList().forEach(menuId -> systemRoleMenuDao.grantMenu(role, menuId));
        }
        cleanAuthService.clearLoginUserCacheByRole(role.getId());
        return new SimpleMessage(ErrorCodeEnum.OK);
    }
}
